package com.zero.java.base.stream;

import com.zero.java.base.model.City;

import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.*;
import java.util.stream.Collectors;
import java.util.stream.Stream;


public class StreamAPIDemo {

	private static final String fileName = "cfg/citys.txt";

	public static void main(String[] args) throws Exception {

		// summingInt
		Map<String, Integer> stateToPopulation = readCity(fileName)
				.collect(Collectors.groupingBy(City::getState, Collectors.summingInt(City::getPopulation)));
		System.out.println(stateToPopulation);

		// maxBy
		Map<String, Optional<City>> stateToMaxPopulation = readCity(fileName).collect(
				Collectors.groupingBy(City::getState, Collectors.maxBy(Comparator.comparing(City::getPopulation))));
		System.out.println(stateToMaxPopulation);

		// mapping
		Map<String, Optional<String>> stateToLongestCityName = readCity(fileName)
				.collect(Collectors.groupingBy(City::getState,
						Collectors.mapping(City::getName, Collectors.minBy(Comparator.comparing(String::length)))));
		System.out.println(stateToLongestCityName);

		// toSet()
		Stream<Locale> locales = Stream.of(Locale.getAvailableLocales());
		Map<String, Set<String>> countryToLanguage = locales.collect(Collectors.groupingBy(Locale::getDisplayCountry,
				Collectors.mapping(Locale::getDisplayLanguage, Collectors.toSet())));
		System.out.println(countryToLanguage);

		//summarizingInt
		Map<String, IntSummaryStatistics> stateToCityPopulationSummary = readCity(fileName)
				.collect(Collectors.groupingBy(City::getState, Collectors.summarizingInt(City::getPopulation)));
		IntSummaryStatistics summaryStatistics = stateToCityPopulationSummary.get("Asia");
		long sum = summaryStatistics.getSum();
		System.out.println(sum);
		System.out.println(stateToCityPopulationSummary);

		//reducing
		Map<String, String> stateToCityNames = readCity(fileName).collect(Collectors.groupingBy(City::getState,
				Collectors.reducing("", City::getName, (s, t) -> s.length() == 0 ? t : s + "," + t)));
		System.out.println(stateToCityNames);

		Map<String, String> stateToCityNames2 = readCity(fileName).collect(
				Collectors.groupingBy(City::getState, Collectors.mapping(City::getName, Collectors.joining(","))));
		System.out.println(stateToCityNames2);

	}

	/**
     * 把文件内容解析成City对象
	 * @param fileName
     * @return
     * @throws Exception
	 */
	public static Stream<City> readCity(String fileName) throws Exception {

		Stream<String> cityLines = Files.lines(Paths.get(fileName));
		Stream<City> cityStream = cityLines.map(l -> l.split(","))
				.map(a -> new City(a[0], a[1], Integer.parseInt(a[2])));
		return cityStream;
	}
}
